'''
使用selenium从web批量导出日志
'''
import time
from selenium import webdriver
from selenium.webdriver.chrome.service import Service
from selenium.webdriver.chrome.options import Options
from selenium.webdriver.common.by import By
from selenium.webdriver.common.keys import Keys
from selenium.webdriver.support.ui import WebDriverWait
from selenium.webdriver.support import expected_conditions as EC

class ExportLog:
    def __init__(self, login_url, user_name, user_passwd) -> None:
        self.login_url = login_url
        self.user_name = user_name
        self.user_passwd = user_passwd
        self.driver = None
        self.service = None
        self.zones = []
        self.zone_sites = {}

    def start_session(self) -> webdriver:
        chrome_dirver_path = "S:\\Code\\my_code\\MyPractice\\projects\\python\\device_log_export_from_web\\chrome_tools\\chromedriver\\chromedriver.exe"
        self.service = Service(chrome_dirver_path)
        self.service.start()

        options = Options()
        options.binary_location = "S:\\Code\\my_code\\MyPractice\\projects\\python\\device_log_export_from_web\\chrome_tools\\chrome\\chrome.exe"
        options.add_argument('--enable-chrome-browser-cloud-management')
        options.add_argument('-ignore-certificate-errors')
        options.add_argument('-ignore -ssl-errors')
        self.driver = webdriver.Remote(self.service.service_url, options=options)

        print(f"create session sucess! {self.driver}")

    
    def run(self):
        try:
            # 启动会话
            self.start_session()

            # 模拟登录
            self.login()

            # 获取所有的区域列表
            self.get_zones()

            zone_name = "成都城投"

            # self.change_to_zone('zone-glds123')
            self.change_to_zone(zone_name)

            # self.get_zone_sites()
            # 定位到设备日志导出页面
            self.navigate_to_log_export_page()

            # 获取到所有站点信息
            #   刷选出所有站点
            self.get_all_sites_of_zone(zone_name)

            # 针对每一个站点，新建一个导出日志的任务
            for item in self.zone_sites[zone_name]:
                self.export_logs(item)

        except Exception as err:
            print(f"!!!!! EROOR: {str(err)} !!!")
            pass

    def login(self):
        #self.login_url = 'www.baidu.com'
        print(f"will get {self.login_url} ...")
        self.driver.get(self.login_url)
        print(f"get {self.login_url} success!")

        # 等待让登录页面加载出来
        time.sleep(3)

        user_box = self.driver.find_element(by=By.ID, value="username")
        user_box.send_keys(self.user_name)
        passwd_box = self.driver.find_element(by=By.ID, value="password")
        passwd_box.send_keys(self.user_passwd)

        time.sleep(2)
        submit_class_name = "ant-btn ant-btn-primary ant-btn-two-chinese-chars w-full login-btn rounded-lg"
        submit_class_name = submit_class_name.replace(' ', '.')
        submit_box = self.driver.find_element(by=By.CLASS_NAME, value=submit_class_name)
        submit_box.click()
        
        # 等待让登录之后的界面加载出来
        time.sleep(5)

        print("login sucess!")
    
    def get_zones(self):
        print("now get zones name....")
        time.sleep(6)

        # 我知道了
        known = 'dpdesign-btn dpdesign-btn-default float-right rounded text-sm !text-primaryblue !bg-white dpdesign-btn-wrap dpdesign-btn-solid'
        known = known.replace(' ', '.')

        select_list = self.driver.find_element(by=By.CLASS_NAME, value='dp-select-selector')
        select_list.click()
        time.sleep(0.5)

        # 获取所有的zone名称
        zone_class_name = 'tenant-dropdown-content'
        zones_name = self.driver.find_elements(by=By.CLASS_NAME, value=zone_class_name)
        print(f"zone数量为: {len(zones_name)}")
        for name in zones_name:
            self.zones.append(name.text)


        select_list.click()
    
    def click_zones_listbox(self, double_click=False):
        '''
        点击区域的下拉列表
        '''
        select_list = self.driver.find_element(by=By.CLASS_NAME, value='dp-select-selector')
        select_list.click()

        if double_click:
            time.sleep(0.5)
            select_list.click()
    
    def change_to_zone(self, zone_name):
        '''
        切换到指定的zone
        '''
        time.sleep(0.5)
        # 将下拉列表选出
        select_list = self.driver.find_element(by=By.CLASS_NAME, value='dp-select-selector')
        select_list.click()
        select_class_name = 'dp-select-dropdown dp-select-dropdown-placement-bottomLeft'
        select_class_name = select_class_name.replace(' ', '.')
        WebDriverWait(self.driver, 10).until(EC.visibility_of_all_elements_located((By.CLASS_NAME, select_class_name)))

        print(f"now try to swich zone: {zone_name}!")
        time.sleep(5)
        
        # 定位到下拉列表的form表单
        form_class_name = 'tenant-dropdown' # 'dp-form dp-form-horizontal'
        # form_class_name = form_class_name.replace(' ', '.')
        form_list = self.driver.find_element(by=By.CLASS_NAME, value=form_class_name)
        self.driver.execute_script("arguments[0].focus();", form_list) # 焦点在form表单

        # 找到待匹配的元素
        zone_elements = form_list.find_elements(By.CLASS_NAME, value="tenant-dropdown-content")
        print(f"=====找到 {len(zone_elements)} 个区域元素")
        for ele in zone_elements:
            # print(f"=====当前区域 {ele.text}...")
            if zone_name == ele.text:
                #if ele.is_enable():
                ele.click()
                print(f"切换到{zone_name}成功")
                time.sleep(5)
                return True
        
        print(f"切换到{zone_name}失败!")
        return False
    
    def navigate_to_log_export_page(self):
        # 定位到设备管理导航栏
        if not self.navigate_to('dp-menu-submenu dp-menu-submenu-vertical main-item single', 'submenu-title', '设备管理'):
            return False
        
        # 定位到设备日志导航栏
        if not self.navigate_to('dp-menu-submenu dp-menu-submenu-vertical sub-item parent', 'submenu-title', '设备日志'):
            return False
        
        # 定位到设备日志导出页面
        if not self.navigate_to('dp-menu-item-group sub-item parent', 'dp-menu-item leaf-item single', '设备日志导出'):
            return False
        
        print(f"已经成功定位到日志导出页面")
        return True

    
    def navigate_to(self, parent_class_name, target_class_name, target_attr_name):
        time.sleep(0.5)
        parent_class_name = parent_class_name.replace(' ', '.')
        ele_list_found = self.driver.find_elements(by=By.CLASS_NAME, value=parent_class_name)
        for ele in ele_list_found:
            target_class_name = target_class_name.replace(' ', '.')
            target_list_found = ele.find_elements(by=By.CLASS_NAME, value=target_class_name)
            for target in target_list_found:
                attr_value = target.get_attribute('title')
                print(f"[{target_attr_name}]: 获取到元素值[{attr_value}]成功!")
                if target_attr_name == attr_value:
                    if ele.is_enabled():
                        ele.click()
                        print(f"导航到[{target_attr_name}]成功!")
                        return True
        print(f"导航到[{target_attr_name}]失败!，参数: {parent_class_name}, {target_class_name}")
        return False
    
    def get_all_sites_of_zone(self, zone_name):
        time.sleep(5)
        # 点击"新建任务"
        new_task_class_name = 'ant-btn ant-btn-primary ml-4'
        new_task_class_name = new_task_class_name.replace(' ', '.')
        new_task_button = self.driver.find_element(by=By.CLASS_NAME, value=new_task_class_name)
        if new_task_button.is_enabled():
            new_task_button.click()
        else:
            print(f"未找到新建任务按钮，获取站点列表失败")
            return
        time.sleep(2)

        # 选择设备类型是"控制器"
        equip_choose = '控制器'

        equip_input_id = 'neType'
        equip_input_ele = self.driver.find_element(by=By.ID, value=equip_input_id)
        equip_input_ele.send_keys(equip_choose)
        time.sleep(2)

        equip_input_ele.send_keys(Keys.ENTER)
        time.sleep(2)

        # 点击查询
        time.sleep(2)
        query_button_class_name = 'ant-btn ant-btn-primary mr-4'
        query_button_class_name = query_button_class_name.replace(' ', '.')
        query_button = self.driver.find_element(by=By.CLASS_NAME, value=query_button_class_name)
        if query_button.is_enabled():
            query_button.click()
        else:
            print(f"未找到查询任务按钮，获取站点列表失败")
            return
        time.sleep(3)

        # 选择100条/页
        choose_items_list_class_name = 'ant-select ant-pagination-options-size-changer ant-select-single ant-select-show-arrow'
        choose_items_list_class_name = choose_items_list_class_name.replace(' ', '.')
        choose_items_list_ele = self.driver.find_element(by=By.CLASS_NAME, value=choose_items_list_class_name)
        choose_items_list_ele.click()

        time.sleep(0.5)
        target_items_a_page = '100 条/页'
        choose_items_for_page_class_name = 'ant-select-item ant-select-item-option'
        choose_items_for_page_class_name = choose_items_for_page_class_name.replace(' ', '.')
        choose_items_for_page_ele = self.driver.find_elements(by=By.CLASS_NAME, value=choose_items_for_page_class_name)
        for ele in choose_items_for_page_ele:
            attr_name = ele.get_attribute('title')
            if attr_name == target_items_a_page:
                ele.click()
                print(f"选择[{target_items_a_page}]成功")
                break
        
        # 定位到表格元素，这里假设表格有一个class_name="ant-table-tbody"
        sites = []
        table = self.driver.find_element(by=By.CLASS_NAME, value='ant-table-tbody')
        # 遍历所有的行
        for row in table.find_elements(by=By.TAG_NAME, value='tr'):
            # 在每一行中遍历所有的单元格
            cols = row.find_elements(by=By.TAG_NAME, value='td')
            #for index in range(1, len(cols)): # 第一列是复选框，跳过。第 2 3 4列分别为站名/设备名/SN
            print(f"站点:[{cols[1].text}], 设备:[{cols[2].text}], SN:[{cols[3].text}]")
            sites.append([cols[1].text, cols[2].text, cols[3].text])
            #for cell in row.find_elements(by=By.TAG_NAME, value='td'):
                # 打印单元格的文本内容
                #print(cell.text)
        self.zone_sites[zone_name] = sites
        
    
    def get_zone_sites(self):
        '''
        获取所有的站点名称列表
        '''
        # 点击"新建任务"
        new_task_class_name = 'ant-btn ant-btn-primary ml-4'
        new_task_class_name = new_task_class_name.replace(' ', '.')
        new_task_buttom = self.driver.find_element(by=By.CLASS_NAME, value=new_task_class_name)
        if new_task_buttom.is_enabled():
            new_task_buttom.click()
        else:
            print(f"未找到新建任务按钮，获取站点列表失败")
            return

        # 选择设备类型是"控制器"
        #   先将焦点放在下拉列表
        time.sleep(0.5)
        select_class_name = 'ant-select ant-select-status-success ant-select-single ant-select-show-arrow ant-select-show-search'
        select_class_name = select_class_name.replace(' ', '.')
        select_list = self.driver.find_element(by=By.CLASS_NAME, value=select_class_name)
        select_list.click()
        time.sleep(1)

        equip_choose = '控制器'
        equip_input_id = 'neType'
        equip_input_ele = self.driver.find_element(by=By.ID, value=equip_input_id)
        equip_input_ele.send_keys(equip_choose)
        time.sleep(2)

        choose_input_equip_id = 'neType_list_0'
        choose_input_equip_ele = self.driver.find_element(by=By.ID, value=choose_input_equip_id)
        choose_input_equip_ele.click()
        time.sleep(2)

    
    def click_submit_to_export_log(self):
        '''
        点击新建导出日志任务的确定
        '''
        button_class_name = 'ant-btn ant-btn-primary'
        button_class_name = button_class_name.replace(' ', '.')
        buttons = self.driver.find_elements(by=By.CLASS_NAME, value=button_class_name)

        text_name = "确 定"
        for button in buttons:
            if button.text == text_name:
                print(f"OK ==== 找到按钮 [{text_name}]")
                # button.click()
                break
    
    def export_logs(self, site):
        # 获取所有的区域列表
        # 遍历区域列表
        #   选择导出日志
        #   获取所有的站点列表
        #       对每一个站点都新建一个任务，任务名称为站点名字+设备ESN
        #       导出日志
        #       保存日志到本地
        pass

    def close(self):
        if self.service:
            #self.service.stop()
            print("service stoped!")
        if self.driver:
            self.driver.close()
            print("driver closed!")

    def __del__(self):
        self.close()
            


if __name__ == '__main__':
    login_url = 'XXX'
    user_name = 'XXX'
    user_passwd = 'XXX'
    
    export_log = ExportLog(login_url, user_name, user_passwd)
    export_log.run()

    print("sleep 50sec ...")
    time.sleep(50)